package com.gitee.wsl.android.timer

import android.os.Handler
import android.os.Looper
import androidx.fragment.app.Fragment
import androidx.lifecycle.Lifecycle
import androidx.lifecycle.LifecycleEventObserver
import androidx.lifecycle.LifecycleOwner
import com.gitee.wsl.time.timeout.Timer
import kotlinx.coroutines.cancel


// </editor-fold>

//<editor-fold desc="生命周期">
/**
 * 自动在指定生命周期后取消[cancel]轮询器
 * @param lifecycleOwner 生命周期持有者, 一般为Activity/Fragment
 * @param lifeEvent 销毁生命周期, 默认为 [Lifecycle.Event.ON_DESTROY] 时停止时停止轮询器
 */
@JvmOverloads
fun Timer.life(
    lifecycleOwner: LifecycleOwner,
    lifeEvent: Lifecycle.Event = Lifecycle.Event.ON_DESTROY
) = apply {
    runMain {
        lifecycleOwner.lifecycle.addObserver(object : LifecycleEventObserver {
            override fun onStateChanged(source: LifecycleOwner, event: Lifecycle.Event) {
                if (lifeEvent == event) cancel()
            }
        })
    }
}

/**
 * 自动在指定生命周期后取消[cancel]轮询器
 * @param lifeEvent 销毁生命周期, 默认为 [Lifecycle.Event.ON_DESTROY] 时停止时停止轮询器
 */
@JvmOverloads
fun Timer.life(
    fragment: Fragment,
    lifeEvent: Lifecycle.Event = Lifecycle.Event.ON_DESTROY
): Timer {
    fragment.viewLifecycleOwnerLiveData.observe(fragment) {
        it?.lifecycle?.addObserver(object : LifecycleEventObserver {
            override fun onStateChanged(source: LifecycleOwner, event: Lifecycle.Event) {
                if (lifeEvent == event) cancel()
            }
        })
    }
    return this
}

/**
 *  当界面不可见时暂停[pause], 当界面可见时继续[resume], 当界面销毁时[cancel]轮询器
 */
fun Timer.onlyResumed(lifecycleOwner: LifecycleOwner) = apply {
    runMain {
        lifecycleOwner.lifecycle.addObserver(object : LifecycleEventObserver {
            override fun onStateChanged(source: LifecycleOwner, event: Lifecycle.Event) {
                when (event) {
                    Lifecycle.Event.ON_RESUME -> resume()
                    Lifecycle.Event.ON_PAUSE -> pause()
                    Lifecycle.Event.ON_DESTROY -> cancel()
                    else -> {}
                }
            }
        })
    }
}
//</editor-fold>

private fun runMain(block: () -> Unit) {
    if (Looper.myLooper() == Looper.getMainLooper()) {
        block()
    } else {
        Handler(Looper.getMainLooper()).post { block() }
    }
}